package cn.piesat.scanning.business.common.algorithm.cimissScan;

import cn.piesat.scanning.business.common.AlgorithmDefineAbstract;
import cn.piesat.scanning.service.DbDmsSchedulerTaskFileRecordService;
import cn.piesat.scanning.utils.CimissInterfaceAPI;
import cn.piesat.scanning.utils.MatchTime;
import cn.piesat.scanning.vo.ResultBean;
import org.apache.commons.lang3.StringUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Component;

import javax.servlet.http.HttpServletResponse;
import java.io.*;
import java.net.MalformedURLException;
import java.net.URL;
import java.net.URLConnection;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.stream.Collectors;

/**
 * @author xhl
 */
@Component
public class CimissScan extends AlgorithmDefineAbstract {

    @Autowired
    private DbDmsSchedulerTaskFileRecordService dbDmsSchedulerTaskFileRecordService;

    @Override
    public void exec(Map<String, Object> params, String taskId) {
        Map<String, String> args = new HashMap<String, String>();
        String dataCode = (String)params.get("dataCode");//资料类型
        String interfaceId=(String)params.get("interfaceId");//调用接口
        String cimissType = (String) params.get("cimissType");//cimiss用户标识
        String elements = (String) params.get("elements");//要素
        String timeType = (String) params.get("timeType");//时间类型
        String dateFormat = (String) params.get("dateFormat");//时间格式{yyyy}{MM}{dd}{HH}{mm}
        String dateRangeFormat = (String) params.get("dateRangeFormat");//时间段格式{yyyy}{MM}{dd}{HH}{mm}
        String outputType = (String) params.get("outputType");//输出类型 file下载文件、db存数据库、txt生成.txt格式文件
        String outputPath = (String) params.get("outputPath");//输出路径
        String dataFormat = (String) params.get("dataFormat");//返回格式
        String dataType = (String) params.get("dataType");//数据类型
        String ip = (String)params.get("ip");//ip地址
        String port = (String)params.get("port");//端口
        String name = (String)params.get("name");//用户名
        String pwd = (String)params.get("pwd");//密码
        String nowDate = "";
        String dateRange = "";
        String fileName = "";

        // 获取实时时间
        if(dateFormat !=null && !dateFormat.equals("")){
            nowDate = MatchTime.match(dateFormat);
        }
        // 获取时间范围
        if(dateRangeFormat !=null && !dateRangeFormat.equals("")){
            dateRange = MatchTime.match(dateRangeFormat);
        }
        // 封装cimiss链接,增加时间或时间范围
        if(!StringUtils.isEmpty(nowDate) && !StringUtils.isEmpty(dateRange)){
            args.put(timeType, "["+nowDate+","+dateRange+"]");
            fileName = nowDate + "_" + dateRange;
        }else if(!StringUtils.isEmpty(nowDate)){
            args.put(timeType, nowDate);
            fileName = nowDate;
        }

        //封装调用参数

        args.put("dataCode", dataCode);
        args.put("interfaceId", interfaceId);
        args.put("elements", elements);
        args.put("dataFormat", dataFormat);
        Map<String, String> changeMap = new HashMap<>();
        //TODO 此处之后用到再改，循环中的fixmap应该是dymap
        for (Map.Entry<String,Object> e : params.entrySet()) {
            changeMap.put(e.getKey(),e.getValue().toString());
        }

        Map<String, String> param = new HashMap<>();
        param.putAll(args);
        param.putAll(changeMap);
        //请求cimiss API接口
        CimissInterfaceAPI cimiss = new CimissInterfaceAPI(ip, port, name, pwd);
        ResultBean resultBean = cimiss.getGridData(param);
        if(resultBean == null){
            return;
        }
        List<Map<String, String>> list = resultBean.getData();
        if(list.isEmpty()) {
            return;
        }
        //判断输出格式
        if("file".equals(outputType)){
            outputFile(list,outputPath,taskId);
        }else if("txt".equals(outputType)){
            createFileTxt(list,outputPath,fileName,outputType,elements,taskId);
        }
    }

    public void outputFile(List<Map<String, String>> list,String outputPath,String taskId){
        List<String> fileNameList = list.stream().map(item -> {
            return item.get("FILE_NAME");
        }).collect(Collectors.toList());
        dbDmsSchedulerTaskFileRecordService.prepareDataByFileNameList(taskId,fileNameList);
        for (Map<String, String> map : list) {
            dbDmsSchedulerTaskFileRecordService.dataExecution(taskId,map.get("FILE_NAME"));
            String name = map.get("FILE_NAME");
            String url = map.get("FILE_URL");
            if(StringUtils.isEmpty(name) && StringUtils.isEmpty(url)) {
                return;
            }
            try {
                downloadNet(null,url,name,outputPath);
                dbDmsSchedulerTaskFileRecordService.dataResults(taskId,map.get("FILE_NAME"),true);
            } catch (MalformedURLException e) {
                dbDmsSchedulerTaskFileRecordService.dataResults(taskId,map.get("FILE_NAME"),false);
                e.printStackTrace();
            }
        }
    }

    public void createFileTxt(List<Map<String, String>> list,String outputPath,String fileName,String outputType,String elements,String taskId){
        List<String> fileNameList = new ArrayList<>();
        fileNameList.add(fileName);
        dbDmsSchedulerTaskFileRecordService.prepareDataByFileNameList(taskId,fileNameList);
        FileWriter writer = null;
        StringBuffer buffer = null;
        dbDmsSchedulerTaskFileRecordService.dataExecution(taskId,fileName);
        try {
            String[] elementsSplit = elements.split(",");
            File file = new File(outputPath);
            if(!file.exists()){
                file.mkdirs();
            }
            outputPath = outputPath + File.separator + fileName + "." + outputType;

            File outputPathFile = new File(outputPath);

            if(!outputPathFile.exists()){
                outputPathFile.createNewFile();
            }
            writer = new FileWriter(outputPathFile, true);
            for (Map<String, String> map : list) {
                buffer = new StringBuffer();
                for (int i = 0; i < elementsSplit.length; i++) {
                    buffer.append("  "+map.get(elementsSplit[i]));
                }
                buffer.append("\r\n");
                writer.write(buffer.toString());
            }
            writer.close();
            dbDmsSchedulerTaskFileRecordService.dataResults(taskId,fileName,true);
        } catch (IOException e) {
            dbDmsSchedulerTaskFileRecordService.dataResults(taskId,fileName,false);
            e.printStackTrace();
        }

    }


    /**
     * 下载数据
     * @param response
     * @param u 下载数据url地址
     * @param name 文件名称
     * @param outResultPath 输出目录
     * @throws MalformedURLException
     */
    public String downloadNet(HttpServletResponse response, String u, String name, String outResultPath) throws MalformedURLException {
        int bytesum = 0;
        int byteread = 0;
        URL url = new URL(u);
        String outFilePath = outResultPath + File.separator + name;
        File file = new File(outFilePath);
        try {
            if (!file.exists()) {
                file.createNewFile();
            }
            URLConnection conn = url.openConnection();
            InputStream inStream = conn.getInputStream();
            FileOutputStream fs = new FileOutputStream(outFilePath);

            byte[] buffer = new byte[1204];
            int length;
            while((byteread=inStream.read(buffer))!=-1){
                bytesum += byteread;
                fs.write(buffer,0,byteread);
            }
            fs.close();
        } catch (FileNotFoundException e) {
            e.printStackTrace();
        }catch (IOException e) {
            e.printStackTrace();
        }
        return outFilePath;
    }
}
